﻿
//------------------------------------------------------------
// shaco Framework
// Copyright © 2017-2021 chang.liu All rights reserved.
// Feedback: 449612236@qq.com
//------------------------------------------------------------

using System.Collections;
using shaco.Base;

namespace shaco
{
    public interface IResources : shaco.Base.IGameInstance
    {
        string currentPackageName { get; }

        /// <summary>
        /// 同步加载资源
        /// <param name="path">加载路径</param>
        /// <return>加载完毕的资源，如果为空表示资源加载失败</return>
        /// </summary>
        IResourceHandle Load(string path, System.Type type);
        IResourceHandle Load<T>(string path) where T : UnityEngine.Object;
        IResourceHandle LoadAsync<T>(string path) where T : UnityEngine.Object;

        /// <summary>
        /// 同步加载一个目录或者AssetBundle所有资源资源
        /// <param name="path">加载路径</param>
        /// <return>加载完毕的资源，如果为空表示资源加载失败</return>
        /// </summary>
        IAllResourceHandle LoadAll<T>(string path) where T : UnityEngine.Object;
        IAllResourceHandle LoadAllAsync<T>(string path) where T : UnityEngine.Object;

        /// <summary>
        /// 查看资源是否存在
        /// </summary>
        bool Exists(string path);
        bool Exists(IResourceHandleBase handle);

        /// <summary>
        /// 释放资源引用
        /// <param name="handle">资源请求对象</param>
        /// </summary>
        void Release(IResourceHandleBase handle);

        /// <summary>
        /// 尝试卸载资源
        /// <param name="handle">资源请求对象</param>
        /// </summary>
        void TryUnloadUnusedAsset(IResourceHandleBase handle);

        /// <summary>
        /// 卸载不再使用资源，用不用协程访问均可调用
        /// </summary>
        IEnumerator UnloadUnusedAssetsAsync();

        /// <summary>
        /// 设置当前使用的资源包
        /// <param name="packageName">资源所属资源包名称</param>
        /// </summary>
        void SetCurrentPackageName(string packageName);
    }
}

static public class ExtensionsResources
{
    static public T LoadEx<T>(this shaco.IResources res, string path) where T : UnityEngine.Object
    {
        return res.Load<T>(path)?.assetObject as T;
    }

    static public T LoadExWithDefaultPackage<T>(this shaco.IResources res, string path) where T : UnityEngine.Object
    {
#if UNITY_EDITOR
        return UnityEditor.AssetDatabase.LoadAssetAtPath<T>(path);
#else
        return LoadWithOtherPackage<T>(res, path, "DefaultPackage")?.assetObject as T;
#endif
    }

    static public IResourceHandle LoadWithOtherPackage<T>(this shaco.IResources res, string path, string packageName) where T : UnityEngine.Object
    {
        var oldPackageName = res.currentPackageName;
        res.SetCurrentPackageName(packageName);
        var retValue = res.Load<T>(path);
        res.SetCurrentPackageName(oldPackageName);
        return retValue;
    }
}
